﻿using Common;
using Common.Communications;
using Common.Enums.OpticalEnums;
using Common.Model;
using Newtonsoft.Json;
using RcsService.ApiServices;
using RollerControllerService;
using Serilog;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.CompilerServices;
using System.Text;
using System.Threading.Tasks;

namespace RcsService
{
    /// <summary>
    /// Rcs调用服务总入口服务
    /// </summary>
    public class TransferRcsService
    {
        #region 事件
        public event Func<string,OpticalMsgType,string, Task> ResultEvent;

        public event Func<string, string, Task> RollerControlEvent;
        #endregion

        #region 属性
        private List<ProtocolModel> protocolInfos = new List<ProtocolModel>();

        private RcsServiceSettingModel rcsServiceComInfo = new RcsServiceSettingModel();
        #endregion

        #region 构造
        public TransferRcsService(Func<string,OpticalMsgType,string,Task> resultProcess) 
        {
            InitRcsComSettingInfo();
            InitRcsApiSettingInfo();
            ResultEvent += resultProcess;
        }
        #endregion

        #region private
        private void InitRcsComSettingInfo()
        {
            var rcsSetting = AppSetting.Instance.settingSingleModels.FirstOrDefault(s => s.SettingType == ConstString.RcsServiceKey);
            if (rcsSetting is null)
            {
                Log.Error($"Rcs服务通信参数配置不存在");
                return;
            }
            try
            {
                if (rcsSetting.ModelType != typeof(RcsServiceSettingModel))
                {
                    Log.Error($"Rcs服务通信参数配置错误");
                    return;
                }
                var infos = JsonConvert.DeserializeObject(rcsSetting.Values, rcsSetting.ModelType);
                rcsServiceComInfo = infos as RcsServiceSettingModel;
            }
            catch (Exception ex)
            {
                Log.Error($"Rcs服务通信参数读取异常");
            }
        }
        /// <summary>
        /// 读取解析RcsApi接口的配置信息
        /// </summary>
        private void InitRcsApiSettingInfo()
        {
            var rcsSetting = AppSetting.Instance.settingMultipleModels.FirstOrDefault(s => s.SettingType == ConstString.ProtocalRcsKey);
            if (rcsSetting is null)
            {
                Log.Error($"RcsApi服务配置不存在");
                return;
            }
            try
            {
                if (rcsSetting.ModelType != typeof(List<ProtocolModel>))
                {
                    Log.Error($"RcsApi服务配置错误");
                    return;
                }
                var infos = JsonConvert.DeserializeObject(rcsSetting.Values, rcsSetting.ModelType);
                protocolInfos = infos as List<ProtocolModel>;
            }
            catch (Exception ex)
            {
                Log.Error($"RcsApi服务配置读取异常");
            }
        }
        #endregion

        /// <summary>
        /// 光通信消息触发事件
        /// </summary>
        /// <returns></returns>
        public async Task MsgProcess(TcpReciveModel model)
        {
            try
            {
                if (model is null)
                {
                    Log.Error($"光通信接收数据为空!");
                    return;
                }
                var msgData = GetMsgInfo(model.Msg);
                if (string.IsNullOrEmpty(msgData))
                {
                    Log.Error($"光通信接收数据错误!");
                    return;
                }
                var info = JsonConvert.DeserializeObject<OpticalInfoModel>(msgData);
                if (info is null || string.IsNullOrEmpty(info.funCode) || info.data.Length != info.dataLen)
                {
                    Log.Error($"光通信数据错误!");
                    return;
                }
                await RcsApiServiceAnalysis(info.funCode,info.type,info.data,info.number);
            }
            catch (Exception ex)
            {
                Log.Error($"光通信数据转换失败!{ex.Message}");
                return;
            }
        }

        private string GetMsgInfo(string message)
        {
            if (string.IsNullOrEmpty(message))
            {
                return null;
            }
            if (!message.Contains(ConstString.Termination))
            {
                return null;
            }
            var infos = message.Split(ConstString.Termination);
            if (infos.Length != 2)
            {
                return null;
            }
            return infos[0];
        }

        /// <summary>
        /// 解析光通信接收的报文
        /// </summary>
        /// <param name="code"></param>
        /// <param name="msg"></param>
        /// <returns></returns>
        private async Task RcsApiServiceAnalysis(string code,OpticalMsgType type,string msg,string reqCode)
        {
            switch (type)
            {
                //WCS发的反馈RCS请求的数据
                case OpticalMsgType.Result:
                    ResultEvent?.Invoke(reqCode, type, msg);
                    break;
                //WCS访问的RCS的服务
                case OpticalMsgType.call:
                    await RcsApiProcessAsync(code,type, msg, reqCode);
                    break;
                //滚筒报文处理
                case OpticalMsgType.Roller:
                    RollerControlEvent?.Invoke(reqCode,msg);
                    break;
            }
        }

        private async Task RcsApiProcessAsync(string code, OpticalMsgType type, string msg, string reqCode)
        {
            
            var protocolInfo = protocolInfos.FirstOrDefault(p => p.Functioncode == code);
            OpticalInfoModel sendModel = new OpticalInfoModel();
            sendModel.funCode = code;
            sendModel.number = reqCode;
            sendModel.EqCode = AppSetting.Instance.EqCode;
            sendModel.type = OpticalMsgType.Result;
            if (protocolInfo is null)
            {
                Log.Error($"功能码{code}未配置相应的RcsApi服务");
                ResultInfoModel data = new ResultInfoModel();
                data.ResultState = Common.Enums.ResultTypeEnum.Error;
                data.ErrMsg = $"功能码{code}未配置相应的RcsApi服务";
                string result = JsonConvert.SerializeObject(data);
                sendModel.data = result;
                sendModel.dataLen = result.Length;
                var sendErrMsg = JsonConvert.SerializeObject(sendModel) + ConstString.Termination;
                ResultEvent?.Invoke(reqCode, type, sendErrMsg);
                return;
            }
            ComRcsApiService comRcsApiService = new ComRcsApiService();
            var info = await comRcsApiService.RcsApiProcess(msg, rcsServiceComInfo, protocolInfo.RcsApiName);
            sendModel.data = info;
            sendModel.dataLen = info.Length;
            var sendMsg = JsonConvert.SerializeObject(sendModel) + ConstString.Termination;
            ResultEvent?.Invoke(reqCode, type, sendMsg);
        }
    }
}
